// dllmain.cpp : Defines the entry point for the DLL application.
#include "stdafx.h"
#include <windows.h>
#define INCL_WINSOCK_API_TYPEDEFS 1
#include <WinSock2.h>
#include <tchar.h>
#include <stdio.h>
#include <Hooker/hooker.h>

#pragma comment(lib, "Ws2_32")


hooker::RestoreThunk<LPFN_SEND>	l_restoreThunkForSend;
hooker::RestoreThunk<LPFN_RECV>	l_restoreThunkForRecv;
hooker::RestoreThunk<LPFN_CONNECT>	l_restoreThunkForConnect;

int
	WSAAPI
	SendHooked(
	__in SOCKET s,
	__in_bcount(len) const char FAR * buf,
	__in int len,
	__in int flags
	)
{
	printf("%s", __FUNCTION__);
	
	auto result = ((LPFN_SEND)(l_restoreThunkForSend.savedMachineCode))(s,buf,len,flags);	
	
	return result;
}

int
	WSAAPI
	RecvHooked(
	__in SOCKET s,
	__out_bcount_part(len, return) __out_data_source(NETWORK) char FAR * buf,
	__in int len,
	__in int flags
	)
{
	printf("%s", __FUNCTION__);
	
	auto result = ((LPFN_RECV)(l_restoreThunkForRecv.savedMachineCode))(s,buf,len,flags);
	
	return result;
}

int
	WSAAPI
	ConnectHooked(
	__in SOCKET s,
	__in_bcount(namelen) const struct sockaddr FAR * name,
	__in int namelen
	)
{
	printf("%s", __FUNCTION__);
	
	auto result = ((LPFN_CONNECT)(l_restoreThunkForConnect.savedMachineCode))(s,name,namelen);
	
	return result;
}

BOOL APIENTRY DllMain( HMODULE hModule,
                       DWORD  ul_reason_for_call,
                       LPVOID lpReserved
					 )
{
	switch (ul_reason_for_call)
	{
	case DLL_PROCESS_ATTACH:
		{
			l_restoreThunkForSend.hookedFunc = SendHooked;
			l_restoreThunkForSend.originalFunc = send;
			hooker::HookApi(l_restoreThunkForSend);

			l_restoreThunkForConnect.hookedFunc = ConnectHooked;
			l_restoreThunkForConnect.originalFunc = connect;
			hooker::HookApi(l_restoreThunkForConnect);

			l_restoreThunkForRecv.hookedFunc = RecvHooked;
			l_restoreThunkForRecv.originalFunc = recv;
			hooker::HookApi(l_restoreThunkForRecv);
		}
		
		break;
	case DLL_THREAD_ATTACH:
	case DLL_THREAD_DETACH:
	case DLL_PROCESS_DETACH:
		break;
	}
	return TRUE;
}

